home *** CD-ROM | disk | FTP | other *** search
/ Cream of the Crop 21 / Cream of the Crop 21 (Terry Blount) (October 1996).iso / program / srcbkvt.zip / 20_20_4.ASC next >
Text File  |  1996-07-08  |  6KB  |  258 lines

  1. _20/20_
  2. by Al Williams
  3.  
  4. Listing One
  5. { Shared memory component -- Williams }
  6. unit shdmem;
  7.  
  8. interface
  9. uses Windows, Messages, Classes, Controls,SysUtils, DsgnIntf, Forms, Dialogs;
  10.  
  11. type
  12.  
  13. TShareMem=class(TComponent)
  14. private
  15.   Ffilename : TFileName;  { File name }
  16.   FDeleteFlag : Bool;     { Delete on close? }
  17.   FFirstUser : Bool;      { First user? }
  18.   FNewFile : Bool;        { New file? }
  19.   fileh : THandle;        { File handle }
  20.   fmap : THandle;         { Handle to map }
  21.   addr : PChar;           { Base address }
  22.   Fcount : Integer;       { Number of strings }
  23.   FSize : Integer;        { Size of each string }
  24.   Mutex : THandle;        { Access Mutex }
  25.   FValid : Bool;          { Good flag }
  26. protected
  27.   { no protected declarations }
  28. public
  29.   constructor Create(obj : TComponent); override;
  30.   destructor Destroy; override;
  31.   procedure Loaded; override;
  32.   procedure UnLock;
  33.   procedure Clear;
  34.   function Rcl(n : integer;var s : String) : Bool;
  35.   function Sto(n : integer; s: String) : Bool;
  36.   function Lock(timeout : integer) : Bool;
  37.   Property FirstUser : Bool read FFirstUser;
  38.   Property NewFile: Bool read FNewFile;
  39.   Property FileHandle : THandle read fileh;
  40.   Property Valid : Bool read FValid;
  41. published
  42.   property Count : Integer read FCount write FCount default 100;
  43.   property Size : Integer read FSize write FSize default 256;
  44.   property Filename : TFileName read FFilename write FFilename;
  45.   Property DeleteFlag : Bool read FDeleteFlag write FDeleteFlag;
  46. end;
  47.  
  48. procedure Register;
  49.  
  50. implementation
  51. procedure Register;
  52. begin
  53.   RegisterComponents('Samples', [TShareMem]);
  54. end;
  55.  
  56. constructor TShareMem.Create(obj : TComponent);
  57. begin
  58.   inherited Create(obj);
  59. { Default setup }
  60.   FCount:=100;
  61.   FSize:=256;
  62.   Mutex:=0;
  63.   fileh:=-1;
  64.   FDeleteFlag:=False;
  65. end;
  66.  
  67. destructor TShareMem.Destroy;
  68. begin
  69. { Clear items }
  70.    if addr <> nil then
  71.      UnmapViewOfFile(addr);
  72.    if fmap <> 0 then
  73.      CloseHandle(fmap);
  74.    if fileh <> -1 then
  75.      CloseHandle(fileh);
  76.    if Mutex <> 0 then
  77.      CloseHandle(Mutex);
  78.    inherited Destroy;
  79. end;
  80.  
  81. procedure TShareMem.Loaded;
  82. var
  83.   delflag : Integer;
  84. begin
  85.   inherited Loaded;
  86. { Only load if not designing }
  87.   if not (csDesigning in ComponentState) then
  88.   begin
  89. { Create OR open file mapping -- if map exists, this
  90.    just opens it }
  91.   FValid:=True;  { Assume good things }
  92.   if (Fdeleteflag) then
  93.     delflag:=FILE_FLAG_DELETE_ON_CLOSE
  94.   else
  95.     delflag:=0;
  96.   if Ffilename <> '' then
  97.     fileh:=CreateFile(PChar(Ffilename),
  98.       GENERIC_READ or GENERIC_WRITE,0, nil,
  99.       OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL or delflag,0)
  100.   else
  101.     fileh:=THandle(-1);
  102.   if (fileh<>THandle(-1)) and
  103.      (GetLastError=Error_Already_Exists) then
  104.      FNewFile:=False
  105.   else
  106.      FNewFile:=True;
  107.   fmap:=CreateFileMapping(fileh,nil,PAGE_READWRITE,0,
  108.       FCount*FSize,PChar(Name));
  109.   if GetLastError=Error_Already_Exists then
  110.     FFirstUser:=False
  111.   else
  112.     FFirstUser:=True;
  113.   if fileh=THandle(-1) then
  114.     FNewFile:=FFirstUser;
  115.   if (fmap=THandle(0)) then FValid:=False;
  116.   addr:=MapViewOfFile(fmap,FILE_MAP_ALL_ACCESS,0,0,
  117.     FCount*FSize);
  118. { Create locking mutex }
  119.   Mutex:=CreateMutex(nil,FALSE,PChar(Name+'X'));
  120.   if Mutex=THandle(0) then FValid:=False;
  121.  end;
  122. end;
  123.  
  124. function TShareMem.Rcl(n : integer;var s : String) : Bool;
  125. var
  126.     ps:PChar;
  127. begin
  128. { Lock, retrieve, and unlock }
  129.    Lock(INFINITE);
  130.    ps:=PChar(addr+(n*FSize));
  131.    s:=StrPas(ps);
  132.    Unlock;
  133.    result:=True;
  134. end;
  135.  
  136. function TShareMem.Sto(n : integer; s: String) : Bool;
  137. var
  138.    p: PChar;
  139. begin
  140. { Lock, store, and unlock }
  141.   Lock(INFINITE);
  142.   p:=PChar(addr+(n*FSize));
  143.   StrPCopy(p,s);
  144.   Unlock;
  145.   result:=True;
  146. end;
  147.  
  148.  function TShareMem.Lock(timeout : integer) : Bool;
  149.   begin
  150.     result:=WaitForSingleObject(Mutex,timeout)<>0;
  151.   end;
  152.  
  153. procedure TShareMem.Unlock;
  154.   begin
  155.     ReleaseMutex(Mutex);
  156.   end;
  157.  
  158. procedure TShareMem.Clear;
  159. begin
  160.   Lock(INFINITE);
  161.   FillChar(addr^,FCount*FSize,0);
  162.   Unlock;
  163. end;
  164.  
  165. end.
  166.  
  167. Listing Two
  168. { Check in form }
  169. unit vckinfrm;
  170.  
  171. interface
  172.  
  173. uses
  174.   Windows, Messages, SysUtils, Classes, Graphics, Controls,
  175.   Forms, Dialogs, StdCtrls, shdmem;
  176.  
  177. type
  178.   TForm1 = class(TForm)
  179.     Label1: TLabel;
  180.     Name: TEdit;
  181.     Label2: TLabel;
  182.     Company: TEdit;
  183.     Label3: TLabel;
  184.     Visited: TEdit;
  185.     Label4: TLabel;
  186.     Timefield: TEdit;
  187.     Label5: TLabel;
  188.     Key: TEdit;
  189.     CheckIn: TButton;
  190.     Clear: TButton;
  191.     SharedMemory: TShareMem;  { Shared Memory!}
  192.     procedure ClearClick(Sender: TObject);
  193.     procedure CheckInClick(Sender: TObject);
  194.     procedure FormCreate(Sender: TObject);
  195.   private
  196.     function GetNewKey : String;
  197.     { Private declarations }
  198.   public
  199.     { Public declarations }
  200.   end;
  201.  
  202. var
  203.   Form1: TForm1;
  204.  
  205. implementation
  206.  
  207. {$R *.DFM}
  208.  
  209. function TForm1.GetNewKey : String;
  210. var
  211.   k : String;
  212.   keynum : Integer;
  213.   code : Integer;
  214. begin
  215. { Lock shared memory }
  216.   SharedMemory.Lock(INFINITE);
  217. { Get next key }
  218.   SharedMemory.Rcl(0,k);
  219. { Convert to number }
  220.   Val(k,keynum,code);
  221. { Set return value from number (if string is empty
  222.   this ensures a zero return value) }
  223.   result:=IntToStr(keynum);
  224. { Increment next key value and put back }
  225.   keynum:=keynum+1;
  226.   k:=IntToStr(keynum);
  227.   SharedMemory.Sto(0,k);
  228.   SharedMemory.Unlock;
  229. end;
  230.  
  231. procedure TForm1.CheckInClick(Sender: TObject);
  232. begin
  233. timefield.Text:=TimeToStr(Time);
  234. key.Text:=GetNewKey;
  235. { commit to database here }
  236. end;
  237.  
  238. procedure TForm1.ClearClick(Sender: TObject);
  239. begin
  240. timefield.Text:='';
  241. key.Text:='';
  242. name.Text:='';
  243. company.Text:='';
  244. visited.Text:='';
  245. ActiveControl:=Name;
  246. end;
  247.  
  248. procedure TForm1.FormCreate(Sender: TObject);
  249. begin
  250. if SharedMemory.NewFile then
  251.   { clear memory }
  252.   SharedMemory.Clear;
  253. end;
  254.  
  255. end.
  256.  
  257.  
  258.